#include <iostream>
#include <limits>

using std::cout;
using std::endl;
using std::cin;

class Complex
{
public:
    Complex(double dreal = 0.0, double dimag = 0.0)
    : _dreal(dreal)
    , _dimag(dimag)
    {
        cout << "Complex(double = 0.0, double = 0.0)" << endl;
    }

    void print() const
    {
        /* cout << _dreal << " + " << _dimag << "i" << endl; */
        if(0 == _dreal && 0 == _dimag)
        {
            cout << 0 << endl;
        }
        else if(0 == _dreal)
        {
            cout << _dimag << "i" << endl;
        }
        else
        {
            cout << _dreal;
            if(_dimag > 0)
            {
                cout << " + " << _dimag << "i" << endl;
            }
            else if(0 == _dimag)
            {
                cout << endl;
            }
            else
            {
                cout << " - " << (-1) * _dimag << "i" << endl;
            }
        }
    }

    ~Complex()
    {
        cout << "~Complex()" << endl;
    }

    //对于输出流运算符函数而言，不能写成成员函数的形式，因为
    //作为成员函数的时候，在第一个参数的位置会隐含this指针，
    //如果要解决this的影响，可以用this替代rhs，但是这样会改变
    //操作数os与对象的顺序，不满足运算符重载的规则
    //所以输出流运算符函数不能以成员函数的形式进行重载
    /* std::ostream operator<<(std::ostream os); */
    friend std::ostream &operator<<(std::ostream &os, const Complex &rhs);
    friend std::istream &operator>>(std::istream &is, Complex &rhs);
private:
    double _dreal;
    double _dimag;
};

std::ostream &operator<<(std::ostream &os, const Complex &rhs)
{
    cout << "std::ostream &operator<<(std::ostream &, const Complex &)" << endl;
    if(0 == rhs._dreal && 0 == rhs._dimag)
    {
        os << 0 << endl;
    }
    else if(0 == rhs._dreal)
    {
        os << rhs._dimag << "i" << endl;
    }
    else
    {
        os << rhs._dreal;
        if(rhs._dimag > 0)
        {
            os << " + " << rhs._dimag << "i" << endl;
        }
        else if(0 == rhs._dimag)
        {
            os << endl;
        }
        else
        {
            os << " - " << (-1) * rhs._dimag << "i" << endl;
        }
    }

    return os;
}

void readDouble(std::istream &is, double &number)
{
    while(is >> number, !is.eof())//真值表达式
    {
        if(is.bad())
        {
            cout << "stream is bad" << endl;
            return;
        }
        else if(is.fail())
        {
            is.clear();
            is.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
            cout << "pls input double data" << endl;
        }
        else 
        {
            cout << "number = " << number << endl;
            break;
        }
    }
}

std::istream &operator>>(std::istream &is, Complex &rhs)
{
    cout << "std::istream &operator>>(std::istream &, Complex &)" << endl;
    readDouble(is, rhs._dreal);
    readDouble(is, rhs._dimag);
    /* is >> rhs._dreal >> rhs._dimag; */

    return is;
}
void test()
{
    Complex c1(2, 3);
    cout << "c1 = ";
    c1.print();

    cout << endl;
    Complex c2(2, 0);
    cout << "c2 = ";
    c2.print();

    cout << endl;
    Complex c3(2, -3);
    cout << "c3 = ";
    c3.print();

    cout << endl;
    Complex c4(0, 3);
    cout << "c4 = ";
    c4.print();

    cout << endl;
    Complex c5(0, 0);
    cout << "c5 = ";
    c5.print();

    cout << endl;
    Complex c6(0, -3);
    cout << "c6 = ";
    c6.print();

    cout << endl;
    Complex c7(-2, 3);
    cout << "c7 = ";
    c7.print();

    cout << endl;
    Complex c8(-2, 0);
    cout << "c8 = ";
    c8.print();

    cout << endl;
    Complex c9(-2, -3);
    cout << "c9 = ";
    c9.print();
}

void test2()
{
    Complex c(2, 3);
    //原始版本
    /* operator<<(operator<<(cout, "c = "), c).operator<<(endl); */
    cout << "c = " << c << endl;

    /* operator<<(cout, "c = "); */
    /* operator<<(cout, c); */
    /* cout.operator<<(endl); */
    /* cout << "c = " << c << "hello" << 1 << c << endl;//链式编程 */
    cout << endl << endl;
    Complex c2;
    cin >> c2;
    cout << "c2 = " << c2 << endl;
}


int main(int argc, char *argv[])
{
    test2();
    return 0;
}

